home *** CD-ROM | disk | FTP | other *** search
- head 1.5;
- branch ;
- access ;
- symbols ;
- locks ; strict;
- comment @@;
-
-
- 1.5
- date 90.03.30.15.47.27; author douglis; state Exp;
- branches ;
- next 1.4;
-
- 1.4
- date 90.01.12.16.47.59; author douglis; state Exp;
- branches ;
- next 1.3;
-
- 1.3
- date 89.06.16.08.29.00; author brent; state Exp;
- branches ;
- next 1.2;
-
- 1.2
- date 89.04.06.08.24.29; author brent; state Exp;
- branches ;
- next 1.1;
-
- 1.1
- date 88.12.30.14.34.45; author ouster; state Exp;
- branches ;
- next ;
-
-
- desc
- @@
-
-
- 1.5
- log
- @Added infor about Pdev_GetStreamID
- @
- text
- @' $Header: /sprite/src/lib/c/etc/RCS/Pdev.man,v 1.4 90/01/12 16:47:59 douglis Exp Locker: douglis $ SPRITE (Berkeley)
- .so \*(]ltmac.sprite
- .HS Pdev lib
- .BS
- .SH NAME
- Pdev_Open, Pdev_Close, Pdev_SetDefaultHandler, Pdev_SetStreamHandler, Pdev_EnumStreams \- Package for servicing pseudo-devices.
- .SH SYNOPSIS
- \fB#include <pdev.h>\fR
- .sp
- Pdev_Token
- .br
- \fBPdev_Open\fR(\fIname, realNamePtr, reqBufSize, readBufSize, service, clientData\fR)
- .br
- void
- .br
- \fBPdev_Close\fR(\fIpdevToken\fR)
- .br
- int
- .br
- \fBPdev_GetStreamID\fR(\fIpdevToken\fR)
- .br
- int (*
- .br
- \fBPdev_SetDefaultHandler\fR(\fIpdevToken, operation, handler\fR))()
- .br
- int (*
- .br
- \fBPdev_SetStreamHandler\fR(\fIstreamPtr, operation, handler\fR))()
- .br
- int
- .br
- \fBPdev_EnumStreams\fR(\fIpdevToken, func, clientData\fR)
- .SH ARGUMENTS
- .AS Pdev_CallBacks readBufSize
- .AP char *name in
- Name of file to use for pseudo-device.
- .AP char **realNamePtr out
- Where to store pointer to actual pseudo-device file name, or NULL
- if \fIname\fR is to be the complete name of pseudo-device file.
- .AP int reqBufSize in
- The preferred size for request buffers.
- .AP int readBufSize in
- The size for a read buffer. Zero means no read buffering.
- .AP Pdev_CallBacks *service in
- A set of service call-back procedures.
- .AP ClientData clientData in
- Private user-defined data field.
- .AP Pdev_Token pdevToken in
- Token for the pseudo-device returned from \fBPdev_Open\fP.
- .AP Pdev_Stream *streamPtr in
- Handle for a stream to the pseudo-device.
- .AP int operation in
- \fBPDEV_OPEN\fP, \fBPDEV_CLOSE\fR, \fBPDEV_READ\fR, \fBPDEV_WRITE\fR,
- \fBPDEV_IOCTL\fR, \fBPDEV_SET_ATTR\fR, \fBPDEV_GET_ATTR\fR.
- .AP int (*handler)() in
- Service call-back procedure.
- .AP int (*func)() in
- A procedure applied to each stream to the pseudo-device.
- .BE
- .SH Pdev_Open
- .LP
- \fBPdev_Open\fR creates a pseudo-device
- and installs a set of service procedures for it.
- The pseudo-device can subsequently be opened by any number of
- regular (client) processes,
- and the service call-backs are made each time a client process makes
- a file system operation on the pseudo-device.
- Thus the service call-backs implement the standard file system
- operations for the pseudo-device while the Pdev package
- manages the interface between the kernel and the server process.
- .LP
- There are two ways that \fBPdev_Open\fR can pick the name of the file to
- use for the pseudo-device. If \fIrealNamePtr\fR is NULL, then
- \fBPdev_Open\fR uses \fIname\fR as the name. If \fIrealNamePtr\fR isn't
- NULL, then \fBPdev_Open\fR will generate a file name of the form
- \fIhostDir\fB/\fInameXX\fR, where \fIhostDir\fR is the name of
- a standard host-specific directory, \fIname\fR
- is the parameter to this procedure, and \fIXX\fR is a decimal number
- generated by \fBPdev_Open\fR. \fBPdev_Open\fR tries numbers up from 1 until it finds
- one that works. The name of the successful pseudo-device file is
- returned by storing a pointer to it at \fI*realNamePtr\fR; the
- storage for the name is dynamically allocated with \fBmalloc\fR and
- must eventually be freed by the caller.
- .PP
- \fBPdev_Open\fR returns an opaque token that
- is used in calls to \fBPdev_Close\fP, \fBPdev_SetDefaultHandler\fP,
- and \fBPdev_EnumStreams\fP.
- If a pseudo-device couldn't be opened, then NULL is
- returned and \fBpdev_ErrorMsg\fR contains a string
- describing the problem.
- .PP
- After a successful \fBPdev_Open\fP call the Pdev package will set up a
- \fIservice stream\fP whenever a client process
- opens the pseudo-device. Each service stream is identified
- to the call-backs by a \fBPdev_Stream\fP record.
- Thus the pseudo-device can be multiplexed over several clients
- with each client's request comming over a different service stream.
- However, forks and dups are not visible to the pseudo-device server,
- so more than one process might be using any particular service stream.
- .PP
- The \fIreqBufSize\fP is used to configure a request buffer associated
- with each service stream. This size determines how many request messages
- can be buffered before the kernel is forced to wait for them to be
- serviced. More than one request may be outstanding due to asynchronous writes,
- which are described below.
- A minimum size on the request buffer is enforced by the library,
- so zero can be passed in to get a default size (about 1 Kbyte).
- .PP
- The \fIreadBufSize\fP is used to configure an optional read buffer associated
- with each service stream. If this size is non-zero it indicates that
- a read buffer will be used to satisfy client read requests instead
- of using the read service call-back.
- In this case the Pdev package will allocate
- a read buffer each time a service stream is created and pass the address
- of this buffer to the open call-back. After that it is up to the
- server process to manage the read buffer. See the device man page
- for \fBpdev\fP for details.
- .PP
- The \fIclientData\fP parameter to \fBPdev_Open\fP
- is passed to the open call-back as
- described below. It is meant to be used as a pointer back to
- some top-level state of the pseudo-device.
- .LP
- The Pdev package uses the facilities of \fBFs_Dispatch\fR in order to keep
- track of the streams associated with the pseudo-device and ensure
- that Pdev is notified whenever those streams become readable. In order
- to use Pdev, you must also use \fBFs_Dispatch\fR.
- .SH Pdev_Close
- .LP
- \fBPdev_Close\fR shuts down a pseudo-device, closing all the streams
- associated with it and releasing any resources allocated to the
- pseudo-device. As a side-effect the close call-back is made to
- any existing service streams. After this procedure returns, \fIpdevToken\fR
- should never be used again.
- .SH Pdev_GetStreamID
- .LP
- \fBPdev_GetStreamID\fR returns the identifier for the stream
- associated with the token returned by \fBPdev_Open\fP. This may be
- used for stream-oriented calls such as \fBfstat\fP but should not be
- used as the argument to \fBclose\fP (\fBPdev_Close\fP should be used
- instead.)
- .SH "Pdev_EnumStreams"
- .PP
- The \fBPdev_EnumStreams\fP procedure is used to apply a function
- to all the service streams to the pseudo-device. This
- enumeration procedure eliminates the need to keep track of
- each service stream.
- The \fIfunc\fP argument is called on each service stream as follows:
- .DS
- int
- (*func)(streamPtr, clientData)
- Pdev_Stream *streamPtr;
- ClientData clientData;
-
- .DE
- Where \fIstreamPtr\fP identifies the service stream,
- and \fIclientData\fP is what was passed to \fBPdev_EnumStreams\fP.
- \fIfunc\fP should return zero to mean success,
- or a non-zero error status. In the case of an error
- \fBPdev_EnumStreams\fP stops its enumeration and returns the non-zero status.
- .SH "Pdev_SetDefaultHandler"
- .LP
- \fBPdev_SetDefaultHandler\fP is used to set the call-back for individual
- pdev operations.
- It is not normally needed as you can define all
- the call-backs with \fBPdev_Open\fP (or \fBPfs_OpenConnection\fP).
- The call-backs passed to \fBPdev_Open\fP are inherited by
- each service stream that is created. Changing a call-back
- with \fBPdev_SetDefaultHandler\fP changes the call-back for
- all subsequently created service streams. It doesn't affect any
- service streams that are already established.
- This returns the old default call-back.
- .SH Pdev_SetStreamHandler
- .PP
- \fBPdev_SetStreamHandler\fP is used to set a call-back for an
- already existing service stream.
- It returns the old call-back.
- .SH "SERVICE PROCEDURES"
- .ta 1.5i 3.0i 3.5i
- .PP
- The call-back service procedures are given to \fBPdev_Open\fP
- (and \fBPfs_OpenConnection\fP) as a record
- of procedures:
- .DS
- typedef struct {
- int (*open)(); /* PDEV_OPEN */
- int (*read)(); /* PDEV_READ */
- int (*write)(); /* PDEV_WRITE and PDEV_WRITE_ASYNC */
- int (*ioctl)(); /* PDEV_IOCTL */
- int (*close)(); /* PDEV_CLOSE */
- int (*getAttr)(); /* PDEV_GET_ATTR */
- int (*setAttr)(); /* PDEV_SET_ATTR */
- } Pdev_CallBacks;
- .DE
- .PP
- Any of the record elements can
- be NULL to indicate that the operation should be handled by
- a default handler.
- The \fIservice\fP parameter
- itself can also be NULL to indicate default
- handling for all operations. This is only useful during initial test.
- If a client makes an operation for which no service procedure is provided
- it is simply a no-op; it is not an error.
- The global variable \fBpdev_Trace\fP can be set to a non-zero value
- to generate printfs to stderr when
- each service procedure (default or user-supplied) is invoked.
- .LP
- Service procedures should return zero to mean successful completion,
- otherwise they should return an appropriate errno value.
- Additionally, the \fBread\fP and \fBwrite\fP procedures
- use \fBEWOULDBLOCK\fR to indicate incomplete operations.
- This is described further below.
- .LP
- Each service procedure also sets the current select state bits for
- the pseudo-device.
- The select bits are used in the kernel's implementation
- of \fBselect\fR for pseudo-devices. They should be a bitwise or
- combination of \fBFS_READABLE\fR, \fBFS_WRITABLE\fR, and \fBFS_EXCEPTION\fR.
- As well as setting this select state after each client operation,
- it may be set asynchronously with the \fBIOC_PDEV_READY\fP
- \fBioctl\fR command on the service stream.
- .PP
- These same service procedures are used for
- pseudo-device connections into the pseudo-file-system.
- See \fBPfs_Open\fP and \fBPfs_OpenConnection\fP.
- The \fBgetAttr\fP and \fBsetAttr\fP call-backs are only made to
- pseudo-file-system servers.
- For regular pseudo-devices the kernel takes care of all attribute handling.
- .SH open
- .ta 0.5i 3.0i 3.5i
- .DS
- int
- (*service->open)(clientData, streamPtr, readBuffer, flags, procID,
- hostID, uid, selectBitsPtr)
- ClientData clientData; /* Private data passed to Pdev_Open */
- Pdev_Stream *streamPtr; /* Identifies stream to pseudo-device. */
- char *readBuffer; /* Storage for optional read buffer */
- int flags; /* Flags to the open system call. NOTE!
- * These are Sprite flags defined in <fs.h>,
- * not the Unix flags defined in <sys/file.h> */
- int procID; /* ID of process opening the pseudo-device */
- int hostID; /* Host where that process is executing */
- int uid; /* User ID of that process */
- int *selectBitsPtr; /* Return - the initial select state of the process */
- .DE
- .LP
- When a client process makes an \fBopen\fP system call on the pseudo-device
- the Pdev library package invokes the \fBopen\fP service call-back to
- give the server a chance to refuse or
- accept the open by the client process. The return value of the
- open call-back is either 0 for success, or an appropriate errno value.
- .PP
- The \fBopen\fR call-back gets passed the \fIclientData\fP that was given
- to the \fBPdev_Open\fP procedure,
- and a new \fIstreamPtr\fP that is a handle on the service stream
- corresponding to the open by the client.
- \fIstreamPtr\fP is a pointer to a \fBPdev_Stream\fP
- record that contains a \fBclientData\fP field for use by the call-backs,
- and a \fBstreamID\fP field that is used in \fBioctl\fP calls
- on the service stream.
- The possible \fBioctl\fP calls are listed at the end of this man page.
- The \fIstreamPtr\fP gets passed to all the other call-backs,
- and is also passed to \fBPdev_SetStreamHandler\fP.
- .PP
- The parameters also include the
- useFlags passed to the \fBFs_Open\fP system call, and the user ID
- and Sprite hostID of the client process.
- (\fBFs_Open\fR is the Sprite version of \fBopen\fR. The
- flag bits are different and are defined in <fs.h>. Flags passed
- to \fBopen\fP are mapped to the Sprite flag bits you'll get here.)
- If the \fIreadBufSize\fP parameter to \fBPdev_Open\fP was non-zero then
- Pdev allocates \fIreadBuffer\fP and passes it to the open call-back.
- Thus there will be one read buffer for each service stream
- if the server is implementing read buffering.
- .SH close
- .ta 0.5i 3.0i 3.5i
- .DS
- int
- (*service->close)(streamPtr)
- Pdev_Stream *streamPtr; /* Identifies service stream */
- .DE
- .LP
- This is called when a service stream is closed.
- This happens either as a side effect of \fBPdev_Close\fP,
- or when the client has closed is last reference to the service stream.
- (Dups and forks are not visible to the pseudo-device server,
- so there is only one close per open system call by a client process.)
- .SH read
- .ta 0.5i 3.0i 3.5i
- .DS
- int
- (*service->read)(streamPtr, readPtr, freeItPtr, selectBitsPtr, sigPtr)
- Pdev_Stream *streamPtr; /* Identifies service stream */
- Pdev_RWParam *readPtr; /* Read parameter block */
- Boolean *freeItPtr; /* Set to TRUE if buffer should be free'd */
- int *selectBitsPtr; /* Return - select state of the pseudo-device */
- Pdev_Signal *sigPtr; /* Return - signal to generate, if any */
- .DE
- .LP
- The read service procedure is passed a record of type \fBPdev_RWParam\fP
- that indicates the \fBlength\fP, \fBoffset\fP, and \fBbuffer\fP
- for the read.
- The buffer is pre-allocated by the \fBPdev\fP library.
- If the read service procedure wants to use a different buffer
- it can change \fIreadPtr\fB->buffer\fR to reference its own storage.
- If this different storage area ought to be freed after
- the library completes the operation,
- then *\fIfreeItPtr\fR should be set to a non-zero value.
- .PP
- The \fIreadPtr\fB->length\fR record field indicates how much data is requested,
- and it should be updated to reflect the amount of data actually returned.
- If there is no data available on the pseudo-device then the
- read call-back should return \fBEWOULDBLOCK\fR
- and set \fIreadPtr\fB->length\fR to zero.
- This causes the kernel to block the client process until the select
- state of the pseudo-device is changed to indicate readability.
- If there are some bytes available the return value should be zero
- and \fIreadPtr\fB->length\fR set appropriately.
- If the read leaves no additional bytes available
- then the \fBFS_READABLE\fP bit can be cleared from *\fIselectBitsPtr\fP
- in order to block the next read request.
- End-of-file is indicated to the client by a zero return code and
- a zero number of bytes returned.
- .PP
- A signal can be generated in response to a read request by
- setting \fIsigPtr\fB->signal\fR to a non-zero value.
- \fIsigPtr\fB->code\fR can also be set to modify the signal meaning.
- Data can be returned if a signal is generated.
- The client application's system call will complete,
- its signal handler, if any, will be invoked,
- and the system call will be retried.
- .PP
- Note: If there is a read buffer associated with the service stream,
- which is indicated by a non-zero valued \fIreadBufSize\fP
- parameter to \fBPdev_Open\fP,
- then this read call-back is never called.
- Instead the kernel takes data directly
- from the read buffer. The protocol for adding data to the read buffer is
- described in the \fBpdev\fR device man page.
- .SH write
- .ta 0.5i 3.0i 3.5i
- .DS
- int
- (*service->write)(streamPtr, async, writePtr, selectBitsPtr, sigPtr)
- Pdev_Stream *streamPtr; /* Identifies service stream */
- int async; /* TRUE during an asynchronous write */
- Pdev_RWParam *writePtr; /* Write parameter block */
- int *selectBitsPtr; /* Return - select state of the pseudo-device */
- Pdev_Signal *sigPtr; /* Return - signal to generate, if any */
- .DE
- .LP
- The write service procedure is passed a parameter block that
- indicates the \fBlength\fP, \fBoffset\fP, and \fBbuffer\fP
- for the operation, plus various IDs of the application process.
- If \fIasync\fP is \fBFALSE\fP (zero)
- then \fIwritePtr\fB->length\fR should be
- updated to reflect how much data was processed by the service procedure.
- If \fIasync\fP is non-zero it indicates an asynchronous write and the service
- procedure must accept all of the data and the
- return value of \fIwritePtr\fB->length\fR is ignored.
- .PP
- If the server cannot accept all of the data it must return \fBEWOULDBLOCK\fR
- \fIand\fP update \fIwritePtr\fB->length\fR to indicate just how much data
- it accepted. This return value causes the kernel to block the client
- process until the select state of the pseudo-device is changed
- to indicate writability.
- To repeat, returning a short write count and a zero return code will cause the
- kernel to immediately issue another write request to complete
- the client's write operation.
- By also returning \fBEWOULDBLOCK\fR the pseudo-device server forces the
- client process to wait until the pseudo-device becomes writable.
- .LP
- A signal to the client application can be generated as a side effect
- by setting \fIsigPtr\fB->signal\fR to a non-zero value.
- \fIsigPtr\fB->code\fR can be set to modify the signal.
- Data can be accepted by the write service procedure if a signal is generated.
- The client application's write call will complete,
- its signal handler, if any, will be invoked,
- and the write call will be retried.
- .SH ioctl
- .ta 0.5i 3.0i 3.5i
- .DS
- int
- (*service->ioctl)(streamPtr, ioctlPtr, selectBitsPtr, sigPtr)
- Pdev_Stream *streamPtr; /* Set by open service procedure */
- Pdev_IOCParam *ioctlPtr; /* I/O Control parameter block */
- int *selectBitsPtr; /* Return - select state of pdev */
- Pdev_Signal *sigPtr; /* Return - signal to generate, if any */
- .DE
- .LP
- The ioctl service procedure takes a parameter block that specifies
- the \fBcommand\fP, and two buffers,
- one containing input data (\fBinBuffer\fP),
- and one for data returned to the client (\fBoutBuffer\fP).
- The ioctl service has to set \fIioctlPtr\fB->outBufSize\fR to indicate how much
- data is being returned to the client process.
- The \fBPdev_IOCParam\fP struct also contains various processIDs,
- and the \fBformat\fP of the host on which the client
- application is executing.
- .LP
- The pseudo-device server can implement any \fIioctlPtr\fB->command\fR it wants.
- Generic commands are defined in <fs.h>, and other ranges of commands
- for particular devices and pseudo-devices are defined in header
- files in /sprite/src/lib/include/dev.
- .LP
- The input and output data is not byteswapped by the operating system.
- It is the server's responsibility to fix up the input and output
- buffers in the case that the client has a different byte order.
- The local byte order is defined as \fBMACH_BYTE_ORDER\fR by <machparam.h>,
- and the client's byte order and alignment are
- indicated by \fIioctlPtr\fB->format\fR.
- The \fBFmt_Convert\fR library routine can be used to
- swap and align incomming and outgoing buffers.
- .LP
- A signal to the client application can be generated as a side effect
- by setting \fIsigPtr\fB->signal\fR to a non-zero value.
- \fIsigPtr\fB->code\fR can be set to modify the signal.
- .SH getAttr
- .ta 0.5i 3.0i 3.5i
- .DS
- int
- GetAttrProc(streamPtr, attrPtr, selectBitsPtr)
- Pdev_Stream *streamPtr; /* Identifies service stream */
- Fs_Attributes *attrPtr; /* Return - attributes */
- int *selectBitsPtr; /* Return - select state of the pseudo-device */
- .DE
- .LP
- This procedure is called to handle an fstat() call on a file
- in a pseudo-file system. The \fIstreamPtr\fP parameter identifies the
- open stream, and the server should fill in the attributes.
- This call-back is not made to regular pseudo-device servers,
- only to pseudo-file-system servers.
- .SH setAttr
- .ta 3.0i 3.5i
- .DS
- int
- SetAttrProc(streamPtr, flags, uid, gid, attrPtr, selectBitsPtr)
- Pdev_Stream *streamPtr; /* Identifies service stream */
- int flags; /* Indicate what attributes to set */
- int uid; /* Identifies user making the call */
- int gid; /* Identifies group of process */
- Fs_Attributes *attrPtr; /* Attributes to set as indicated by flags */
- int *selectBitsPtr; /* Return - select state of the pseudo-device */
- .DE
- .LP
- This procedure is called to set certain attributes of
- an open file in a pseudo-file system. The \fIstreamPtr\fP
- parameter identifies the open stream.
- The flags argument contains an or'd combinantion of
- \fBFS_SET_TIMES\fR, \fBFS_SET_MODE\fR, \fBFS_SET_OWNER\fR,
- \fBFS_SET_FILE_TYPE\fR, \fBFS_SET_DEVICE\fR
- that indicate what attributes to set. The attribute values are contained
- in \fI*attrPtr\fR. The \fIuid\fR and \fIgid\fR arguments
- identify the calling process.
- This call-back is not made to regular pseudo-device servers,
- only to pseudo-file-system servers.
- .SH Service Stream Ioctls
- .ta 1.0i
- .PP
- The pseudo-device server can make a few \fBFs_IOControl\fP calls on
- its service streams. The details of the calling sequences is described
- in the device man page for pseduo-devices (pdev). The possible
- operations are:
- .IP IOC_PDEV_READY
- Used to change the select state of the pseudo-device. The input buffer
- to Fs_IOControl should contain an or'd combination of
- \fBFS_READABLE\fR, \fBFS_WRITABLE\fR, or \fBFS_EXCEPTION\fR.
- .IP IOC_PDEV_SIGNAL_OWNER
- Used to send a signal to the owning process or process group of the
- pseudo-device. This is useful for implementing interrupt characters
- in tty emulators. No special permission is needed.
- .IP IOC_PDEV_WRITE_BEHIND
- Used to set or unset asynchronous writing.
- .IP IOC_PDEV_BIG_WRITES
- Used to allow or disallow writes larger than the request buffer.
- .IP IOC_PDEV_SET_PTRS
- Used to adjust pointers into the read buffer and the request buffer.
- Users of the Pdev package should only use this to adjust
- read buffer pointers. Leave the request buffer pointers equal to -1
- so you don't mess up the managing of the request buffer.
- .PP
- For example:
- .DS
- status = Fs_IOControl(streamPtr->streamID, IOC_PDEV_READY,
- sizeof(int), &selectBits, 0, NULL);
- .DE
- .SH SEE ALSO
- pdev (devices), Pfs, Swap_Buffer
- .SH KEYWORDS
- pseudo-device
- @
-
-
- 1.4
- log
- @updated byteOrder to format, per current version of struct.
- @
- text
- @d1 1
- a1 1
- ' $Header: /sprite/src/lib/c/etc/RCS/Pdev.man,v 1.3 89/06/16 08:29:00 brent Exp Locker: douglis $ SPRITE (Berkeley)
- d18 4
- d135 7
- @
-
-
- 1.3
- log
- @Updated to document new pseudo-device interface
- @
- text
- @d1 1
- a1 1
- ' $Header: /sprite/src/lib/c/etc/RCS/Pdev.man,v 1.2 89/04/06 08:24:29 brent Exp Locker: brent $ SPRITE (Berkeley)
- d387 1
- a387 1
- and the \fBbyteOrder\fP of the host on which the client
- d399 2
- a400 1
- and the client's byte order is indicated by \fIioctlPtr\fB->byteOrder\fR.
- @
-
-
- 1.2
- log
- @Updated to reflect change in the interface
- @
- text
- @d1 1
- a1 1
- ' $Header: /sprite/src/lib/c/etc/RCS/Pdev_Open.man,v 1.1 88/12/30 14:34:45 ouster Exp $ SPRITE (Berkeley)
- d100 2
- a101 2
- serviced. More than one request may be outstanding due to stream sharing,
- or due to asynchronous writes.
- d227 3
- a229 1
- int flags; /* Flags to the open system call */
- d255 1
- a255 1
- useFlags passed to the \fBopen\fP system call, and the user ID
- d257 3
- d281 1
- a281 2
- (*service->read)(streamPtr, offset, procID, familyID, numBytesPtr,
- bufferPtr,freeItPtr, selectBitsPtr)
- d283 1
- a283 6
- int offset; /* Byte offset at which to read */
- int procID; /* ProcessID of client */
- int familyID; /* FamilyID (process group) of client */
- int *numBytesPtr; /* In/Out - num bytes to read/were read */
- char **bufferPtr; /* Pointer to Buffer to hold data. This
- * can be re-allocated by ReadProc. */
- d286 1
- d289 9
- a297 6
- The read service procedure is passed a pointer to a buffer which it should fill
- with data in order to satisfy the client's read request.
- The read service procedure can either copy data into the preallocated buffer,
- or change the buffer to one of its own choosing.
- If the read service procedure allocates a buffer it can be free'd by
- the Pdev package by setting the *\fIfreeItPtr\fR flag to a non-zero value.
- d299 1
- a299 1
- The *\fInumBytesPtr\fR parameter indicates how much data is requested,
- d303 1
- a303 1
- and set *\fInumBytesPtr\fP to zero.
- d307 1
- a307 1
- and *\fInumBytesPtr\fP set appropriately.
- d314 8
- d333 1
- a333 2
- (*service->write)(streamPtr, async, offset, procID, familyID,
- numBytesPtr, buffer, selectBitsPtr)
- d336 1
- a336 5
- int procID; /* ProcessID of client process */
- int familyID; /* FamilyID (process group) of client */
- int offset; /* Byte offset at which to write */
- int *numBytesPtr; /* In/Out - num bytes to write/were written */
- char *buffer; /* Buffer that holds data written by client */
- d338 1
- d341 5
- a345 3
- The write service procedure is passed a buffer containing the
- data written by the client. If \fIasync\fP is \fBFALSE\fP (zero)
- the *\fInumBytesPtr\fR argument should be
- d349 1
- a349 1
- return value of \fInumBytesPtr\fR is ignored.
- d352 1
- a352 1
- \fIand\fP update \fInumBytesPtr\fP to indicate just how much data
- d361 8
- d373 1
- a373 2
- (*service->ioctl)(streamPtr, command, procID, familyID, byteOrder,
- inSize, inBuffer, outSizePtr, outBuffer, selectBitsPtr)
- d375 1
- a375 8
- int command; /* IOControl command */
- int procID; /* Process ID of calling process */
- int familyID; /* Family ID of calling process */
- int byteOrder; /* Indicates client's byte ordering */
- int inSize; /* Size of inBuffer */
- char *inBuffer; /* Buffer containing input data */
- int *outSizePtr; /* Return - size of outBuffer */
- char *outBuffer; /* Return - Buffer containing result data */
- d377 1
- d380 5
- a384 3
- The ioctl service procedure involves two buffers, one containing
- input data, and one for data returned to the client.
- The ioctlProc has to set *\fIoutSizePtr\fR to indicate how much
- d386 3
- d390 1
- a390 1
- The pseudo-device server can implement any \fIcommand\fP it wants.
- d399 2
- a400 2
- and the client's byte order is indicated by the byteOrder argument.
- The \fBSwap_Buffer\fR library routine can be used to
- d402 4
- @
-
-
- 1.1
- log
- @Initial revision
- @
- text
- @d1 1
- a1 1
- ' $Header: /sprite/doc/ref/lib/c/RCS/Pdev_Open,v 1.1 88/11/14 10:25:25 brent Exp Locker: brent $ SPRITE (Berkeley)
- d3 1
- a3 1
- .HS Pdev_Open libcalls
- d6 1
- a6 1
- Pdev_Open \- open pseudo-device and install service procedures for it.
- d10 19
- a28 2
- ClientData
- \fBPdev_Open\fR(\fIname, realNamePtr, service\fR)
- d30 1
- a30 1
- .AS char realNamePtr
- d36 19
- a54 2
- .AP IntProc *service
- Array of service call-back procedures.
- d56 1
- a56 1
- .SH DESCRIPTION
- d58 9
- a66 15
- \fBPdev_Open\fR creates a pseudo-device and installs a set of service procedures
- for it. The service procedures are called when client processes
- open and use the pseudo-device. The callbacks are given as an array
- of procedures (\fBIntProc\fP). Any of the array elements can
- be NULL to indicate that the operation should be handled by
- a default handler.
- The \fBservice\fP parameter itself can also be NULL to indicate default
- handling for all operations. This is only useful during initial test.
- If a client makes an operation for which no service procedure is provided
- it is simply a no-op; it is not an error.
- The global variable \fBpdevTrace\fP can be set to generate printfs when
- each service procedure (default or user-supplied) is invoked.
- The details of the service procedures
- are described below, after a description of how the pseudo-device's
- name is chosen by \fBPdev_Open\fR.
- d80 4
- a83 3
- .LP
- The return value of \fBPdev_Open\fR is a token for the pseudo-device, which must
- be used in calls to \fBPdev_Close\fR and \fBPdev_Ready\fR.
- d87 32
- d124 72
- d197 34
- a230 26
- The service procedures in the service array are
- indexed by the pseudo-device operation type. Thus
- .DS
- bzero(service, PDEV_NUM_OPS * sizeof(IntProc));
- service[PDEV_OPEN] = MyOpenProc;
- service[PDEV_READ] = MyReadProc;
- .DE
- is a valid initialization for the service array that
- defines open and read callbacks,
- and leaves the other pseudo-device operations as no-ops.
- .LP
- The
- return value of a service procedure will be the return value
- of the corresponding system call by the client,
- with the exception of FS_WOULD_BLOCK as described below.
- .SH PDEV_OPEN
- .DS
- ReturnStatus
- OpenProc(token, flags, pid, hostID, uid, privatePtr, selectBitsPtr)
- ClientData token; /* Token to identify stream to pseudo-device. */
- /* Pass this token to Pdev_Ready */
- int flags; /* Flags to the open system call */
- int pid; /* ID of process opening the pseudo-device */
- int hostID; /* Host where that process is executing */
- int uid; /* User ID of that process */
- ClientData *privatePtr; /* Settable by openProc for its own use */
- a231 1
- /* A combination of FS_READABLE|FS_WRITABLE|FS_EXCEPTION */
- d234 3
- a236 1
- The open service procedure gives the server a chance to refuse or
- d238 44
- a281 30
- open procedure is passed back as the return of the client's
- open system call. The private data pointer can be set by the
- open service procedure to reference state specific to its own
- needs. This pointer is passed back into the other service procedures.
- There is also a token passed into the openProc which distinguishes
- the stream to the pseudo-device. This token is to be used with the
- Pdev_Ready procedure that indicates the stream to the pseudo-device
- is ready for I/O.
- .LP
- The selectBits are used in the kernel's implementation
- of \fBselect()\fR for pseudo-devices. They should be a bitwise or
- combination of FS_READABLE, FS_WRITABLE, and FS_EXCEPTION.
- As well as setting this select state after each client operation,
- it may be set asynchronously with the Pdev_Ready procedure.
- .SH PDEV_CLOSE
- .DS
- ReturnStatus
- CloseProc(private)
- ClientData private; /* Set by openProc */
- .DE
- This is called when the client closes its stream to the pseudo-device.
- Dups and forks are not visible to the pseudo-device server,
- so the CloseProc is only called once when the stream to the pseudo-device
- is really going away.
- .SH PDEV_READ
- .DS
- ReturnStatus
- ReadProc(private, offset, familyID, numBytesPtr, bufferPtr, freeItPtr, selectBitsPtr)
- ClientData private; /* Set by openProc */
- int offset; /* Byte offset at which to read */
- d283 3
- a285 3
- Address *bufferPtr; /* Pointer to Buffer to hold data. This
- * can be re-allocated by ReadProc. */
- Boolean *freeItPtr; /* TRUE if *bufferPtr is dynamically allocated. */
- d291 1
- a291 1
- The read service procedure can either use the preallocated buffer,
- d293 36
- a328 15
- The freeItPtr parameter indicates if the buffer is dynamically allocated.
- The library uses a buffer on the stack which is FS_BLOCK_SIZE bytes long,
- but will dynamically allocate a new one if the read request is for
- more bytes than this. If the service procedure changes the buffer
- it should free the passed in buffer if indicated by *freeItPtr,
- and it should set *freeItPtr appropriately so the library can
- free the buffer after completing the PDEV_READ transaction with the kernel.
- The numBytesPtr indicates how much data is requested, and it should be
- updated to reflect the amount of data actually returned.
- .SH PDEV_WRITE
- .DS
- ReturnStatus
- WriteProc(private, offset, familyID, numBytesPtr, buffer, selectBitsPtr)
- ClientData private; /* Set by openProc */
- int offset; /* Byte offset at which to write */
- d330 1
- a330 1
- Address buffer; /* Buffer that holds data written by client */
- d335 2
- a336 1
- data written by the client. The numBytesPtr argument should be
- d338 30
- a367 14
- .SH PDEV_IOCTL
- .DS
- ReturnStatus
- IoctlProc(private, command, familyID, byteOrder, inSize, inBuffer, outSizePtr,
- outBuffer, selectBitsPtr)
- ClientData private; /*Set by open service procedure*/
- int command; /*IOControl command*/
- int familyID; /*Family ID of calling process*/
- int byteOrder; /*Indicates clients byte ordering */
- int inSize; /*Size of inBuffer*/
- Address inBuffer; /*Buffer containing input data*/
- int *outSizePtr; /*Resutl - size of outBuffer*/
- Address outBuffer; /*Buffer containing result data*/
- int *selectBitsPtr; /*Return - select state of pdev*/
- d372 1
- a372 1
- The ioctlProc has to set *outSizePtr to indicate how much
- d374 82
- a455 5
- This data is not byteswapped by the operating system in the case
- that the client is on a host with different byte-ordering.
- The client's byte order is indicated by the byteOrder argument,
- and the \fBSwap_Buffer\fR library routine can be used to
- swap incomming and outgoing buffers.
- d457 1
- a457 1
- Pdev_Ready, Pdev_Close, Pfs_Open, Swap_Buffer
- @
-